package shop.controller.manage.system;

import org.apache.commons.lang.StringUtils;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.ModelMap;
import org.springframework.web.bind.annotation.ModelAttribute;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.ResponseBody;
import shop.core.BaseController;
import shop.core.LoginUserHolder;
import shop.core.RequestHolder;
import shop.core.Services;
import shop.core.common.bean.JSONResult;
import shop.core.common.bean.ManageContainer;
import shop.core.util.AddressUtils;
import shop.core.util.MD5;
import shop.services.front.organize.OrganizeService;
import shop.services.front.organize.bean.Organize;
import shop.services.manage.system.bean.Menu;
import shop.services.manage.system.bean.MenuItem;
import shop.services.manage.system.bean.Role;
import shop.services.manage.system.bean.User;
import shop.services.manage.system.impl.MenuService;
import shop.services.manage.system.impl.RoleService;
import shop.services.manage.system.impl.UserService;
import shop.services.manage.systemlog.SystemlogService;
import shop.services.manage.systemlog.bean.Systemlog;

import javax.annotation.Resource;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpSession;
import java.util.*;

/**
 * 后台用户管理
 *
 * @author jeeshopfans
 */
@Controller
@RequestMapping("/manage/user")
public class UserAction extends BaseController<User> {
    private static final org.slf4j.Logger logger = LoggerFactory.getLogger(UserAction.class);

    private static final String page_input = "/manage/system/login";
    private static final String page_home = "/manage/system/home";
    private static final String page_toList = "/manage/system/user/userList";
    private static final String page_toAdd = "/manage/system/user/editUser";
    private static final String page_toEdit = "/manage/system/user/editUser";

    public UserAction() {
        super.page_toEdit = page_toEdit;
        super.page_toList = page_toList;
        super.page_toAdd = page_toAdd;
    }

    @Autowired
    private UserService userService;
    @Autowired
    private RoleService roleService;
    @Autowired
    private MenuService menuService;
    @Autowired
    private OrganizeService organizeservice;
    @Resource(name = "systemlogServiceManage")
    private SystemlogService systemlogService;

    @Override
    public Services<User> getService() {
        return userService;
    }

    /**
     * 异步编辑单个对象
     *
     * @param e
     * @param model
     * @return
     * @throws Exception
     */
    @Override
    @RequestMapping("toEditJson")
    @ResponseBody
    public JSONResult toEditJson(@ModelAttribute("e") User e, ModelMap model) throws Exception {
        e = getService().selectOne(e);
        e.setPassword("");
        jsonResult = new JSONResult();
        jsonResult.setData(e);
        return jsonResult;
    }

    /**
     * 跳转登陆页面--后台登陆进入点
     *
     * @param e
     * @param session
     * @return
     */
    @RequestMapping(value = "login", method = RequestMethod.GET)
    public String login(@ModelAttribute("e") User e, HttpSession session) {
        if (session.getAttribute(ManageContainer.manage_session_user_info) != null) {
            Organize organize = (Organize) session.getAttribute("organizeInfo");
            if (organize != null) {
                switch (organize.getStatus()) {
                    case "3":
                        return "redirect:/manage/organize/toAut";
                    case "2":
                        return "redirect:/manage/organize/toAutFalse";
                    case "0":
                        return "redirect:/manage/organize/toAut";
                    default:
                        return "redirect:/manage/organize/toList";
                }
            } else
                return "redirect:/manage/user/home";
        }
        return page_input;
    }

    /**
     * 后台登录
     *
     * @return
     * @throws Exception
     */
    @RequestMapping(value = "login", method = RequestMethod.POST)
    public String login(HttpSession session, @ModelAttribute("e") User e, ModelMap model) throws Exception {
        String errorMsg;
        if (session.getAttribute(ManageContainer.manage_session_user_info) != null) {
            Organize organize = (Organize) session.getAttribute("organizeInfo");
            if (organize != null) {
                switch (organize.getStatus()) {
                    case "3":
                        return "redirect:/manage/organize/toAut";
                    case "2":
                        return "redirect:/manage/organize/toAutFalse";
                    case "0":
                        return "redirect:/manage/organize/toAut";
                    default:
                        return "redirect:/manage/organize/toList";
                }
            } else
                return "redirect:/manage/user/home";
        }

        if (StringUtils.isBlank(e.getUsername()) || StringUtils.isBlank(e.getPassword())) {
            model.addAttribute("errorMsg", "账户和密码不能为空!");
            return page_input;
        }
        logger.info("用户登录:{}", e.getUsername());
        e.setPassword(MD5.md5(e.getPassword()));
        User u = ((UserService) getService()).login(e);
        if (u == null) {
            errorMsg = "登陆失败，账户或密码错误！";
            model.addAttribute("errorMsg", errorMsg);
            return page_input;
        } else if (!u.getStatus().equals(User.user_status_y)) {
            errorMsg = "帐号已被禁用，请联系管理员!";
            model.addAttribute("errorMsg", errorMsg);
            return page_input;
        }
        u.setUsername(e.getUsername());
        // 将user保存在session中
        session.setAttribute(ManageContainer.manage_session_user_info, u);
        //解析用户的数据库权限，以后可以进行DB权限限制
        if (StringUtils.isNotBlank(u.getRole_dbPrivilege())) {
            String[] dbPriArr = u.getRole_dbPrivilege().split(",");
            if (u.getDbPrivilegeMap() == null) {
                u.setDbPrivilegeMap(new HashMap<String, String>());
            } else {
                u.getDbPrivilegeMap().clear();
            }
            if (dbPriArr.length != 0) {
                for (int i = 0; i < dbPriArr.length; i++) {
                    u.getDbPrivilegeMap().put(dbPriArr[i], dbPriArr[i]);
                }
            }
        }
        //用户可访问的菜单写入session
        Collection<MenuItem> userMenus = loadMenus(u);
        session.setAttribute("userMenus", userMenus);
        try {
            loginLog(u, "login");
        } catch (Exception ex) {
            ex.printStackTrace();
        }
        Role role = roleService.selectById(u.getRid());
        if (role.getRole_name().equals("机构账号")) {
            Organize organize = new Organize();
            organize.setPrincipalPhone(u.getUsername());
            organize = organizeservice.selectByPrincipalPhone(organize);
            session.setAttribute("organizeInfo", organize);
//			根据机构审核状态返回不同页面
            switch (organize.getStatus()) {
                case "3":
                    return "redirect:/manage/organize/toAut";
                case "2":
                    return "redirect:/manage/organize/toAutFalse";
                case "0":
                    return "redirect:/manage/organize/toAut";
                default:
                    return "redirect:/manage/organize/toList";
            }
        } else {
            return "redirect:/manage/user/home";
        }
    }

    /**
     * 加载用户菜单
     *
     * @param u
     * @return
     */
    private Collection<MenuItem> loadMenus(User u) {
        /**
		 * 首先，加载顶级目录或页面菜单
		 */
        Map<String, String> param = new HashMap<String, String>();
        if (u != null && u.getRid() != null) {
            param.put("rid", u.getRid());//角色ID
        }
        List<Menu> menus = menuService.selectList(param);
        //创建菜单集合
        LinkedHashMap<String, MenuItem> root = new LinkedHashMap<String, MenuItem>();
        //循环添加菜单到菜单集合
        for (Menu menu : menus) {
            MenuItem item = new MenuItem(menu.getName(), null);
            item.setId(menu.getId());
            item.setPid(menu.getPid());
            item.setMenuType(menu);
            item.setUrl(StringUtils.trimToEmpty(menu.getUrl()));
            item.setOrderNum(menu.getOrderNum());
            if (item.isRootMenu()) {
                root.put(item.getId(), item);
            }
        }
        for (Menu menu : menus) {
            MenuItem item = new MenuItem(menu.getName(), null);
            item.setId(menu.getId());
            item.setPid(menu.getPid());
            item.setMenuType(menu);
            item.setUrl(StringUtils.trimToEmpty(menu.getUrl()));
            item.setOrderNum(menu.getOrderNum());
            if (!item.isRootMenu() && !item.isButton()) {
                MenuItem parentItem = root.get(item.getPid());
                if (parentItem != null) {
                    parentItem.addClild(item);
                } else {
                    logger.warn("菜单项{}({})没有对应的父级菜单", item.getName(), item.getId());
                }
            }
        }
        return root.values();
    }

    /**
     * 跳转到后台首页
     *
     * @return
     */
    @RequestMapping("home")
    public String home() {
        if (LoginUserHolder.getLoginUser() == null) {
            return "redirect:/manage/user/login";
        }
        return page_home;
    }

    /**
     * 系统登陆日志记录
     *
     * @param u
     * @param log
     */
    private void loginLog(User u, String log) {
        Systemlog systemlog = new Systemlog();
        systemlog.setTitle(log);
        systemlog.setContent(log);
        systemlog.setAccount(u.getUsername());
        systemlog.setType(1);
        systemlog.setLoginIP(AddressUtils.getIp(RequestHolder.getRequest()));

        String address = null;
        if (!systemlog.getLoginIP().equals("127.0.0.1") && !systemlog.getLoginIP().equals("localhost")) {
            //获取指定IP的区域位置
            try {
                address = AddressUtils.getAddresses("ip=" + systemlog.getLoginIP(), "utf-8");
            } catch (Exception e) {
                e.printStackTrace();
            }
            systemlog.setLoginArea(address);

            //异地登陆的判断方法为：先比较本次登陆和上次登陆的区域位置，如果不一致，说明是异地登陆；如果获取不到区域，则比较IP地址，如果IP地址和上次的不一致，则是异地登陆
            Systemlog firstSystemlog = systemlogService.selectFirstOne(u.getUsername());
            if (firstSystemlog != null) {
                systemlog.setDiffAreaLogin(Systemlog.systemlog_diffAreaLogin_n);
                if (StringUtils.isNotBlank(address) && StringUtils.isNotBlank(firstSystemlog.getLoginArea())) {
                    if (!address.equals(firstSystemlog.getLoginArea())) {
                        systemlog.setDiffAreaLogin(Systemlog.systemlog_diffAreaLogin_y);
                    }
                } else if (StringUtils.isNotBlank(systemlog.getLoginIP()) && StringUtils.isNotBlank(firstSystemlog.getLoginIP())) {
                    if (!systemlog.getLoginIP().equals(firstSystemlog.getLoginIP())) {
                        systemlog.setDiffAreaLogin(Systemlog.systemlog_diffAreaLogin_y);
                    }
                }

            }
        }
        systemlogService.insert(systemlog);
    }


    /**
     * 异步新增用户
     *
     * @param request
     * @param e
     * @return
     * @throws Exception
     */
    @Override
    @RequestMapping(value = "insertJson", method = RequestMethod.POST)
    @ResponseBody
    public JSONResult insertJson(HttpServletRequest request, @ModelAttribute("e") User e) throws Exception {
        User user = (User) RequestHolder.getSession().getAttribute(ManageContainer.manage_session_user_info);
        jsonResult = new JSONResult();
        e.setCreateAccount(user.getUsername());
        if (StringUtils.isBlank(e.getStatus())) {
            e.setStatus(User.user_status_y);
        }
        e.setPassword(MD5.md5(e.getPassword()));
        getService().insert(e);
        return jsonResult;
    }

    /**
     * 异步新增用户
     *
     * @param request
     * @param e
     * @return
     * @throws Exception
     */
    @Override
    @RequestMapping(value = "updateJson", method = RequestMethod.POST)
    @ResponseBody
    public JSONResult updateJson(HttpServletRequest request, @ModelAttribute("e") User e) throws Exception {
        User user = (User) RequestHolder.getSession().getAttribute(ManageContainer.manage_session_user_info);
        jsonResult = new JSONResult();
        e.setCreateAccount(user.getUsername());
        if (StringUtils.isBlank(e.getStatus())) {
            e.setStatus(User.user_status_y);
        }
        if (!StringUtils.isBlank(e.getPassword())) {
            e.setPassword(MD5.md5(e.getPassword()));
        }
        getService().update(e);
        return jsonResult;
    }

    /**
     * 注销登录
     *
     * @return
     * @throws Exception
     */
    @RequestMapping("logout")
    public String logout(@ModelAttribute("e") User e) throws Exception {
        HttpSession session = RequestHolder.getSession();
        if (session != null) {
            User u = LoginUserHolder.getLoginUser();
            if (u != null && StringUtils.isNotBlank(u.getUsername())) {
                loginLog(u, "loginOut");
            }
            //登出信息设置为null
            session.setAttribute(ManageContainer.manage_session_user_info, null);
            session.setAttribute(ManageContainer.resource_menus, null);
            session.setAttribute(ManageContainer.user_resource_menus_button, null);
        }
        e.clear();
        return page_input;
    }
}